package cn.org.wangchangjiu.sqltomongo.core.analyzer.select_option;

import cn.org.wangchangjiu.sqltomongo.core.analyzer.AbstractAnalyzer;
import cn.org.wangchangjiu.sqltomongo.core.parser.data.LookUpData;
import cn.org.wangchangjiu.sqltomongo.core.parser.data.PartSQLParserData;
import cn.org.wangchangjiu.sqltomongo.core.parser.data.ProjectData;
import cn.org.wangchangjiu.sqltomongo.core.parser.data.TableNameManager;
import org.apache.commons.lang3.StringUtils;
import org.bson.Document;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * @Classname ProjectAnalyzer
 * @Description 投影分析器
 * @Date 2022/8/12 11:54
 * @Created by wangchangjiu
 */
public class ProjectAnalyzer extends AbstractAnalyzer {

    @Override
    public void proceed(List<Document> documents, PartSQLParserData data) {
        List<ProjectData> projectData = data.getProjectData();
        // 分析投影  构建 mongo API
        documents.addAll(analysisProject(projectData, data.getTableNameManager()));
    }


    /**
     * 分析 投影 构建 投影 Mongo API
     *
     * @param projectData
     * @return
     */
    private static List<Document> analysisProject(List<ProjectData> projectData, TableNameManager tableNameManager) {
        Map<String, LookUpData> lookUpDataMap = tableNameManager.getJoinTables();
        String majorTableAlias = tableNameManager.getMajorTableAlias();
        List<Document> documents = new ArrayList<>();

        Document fieldObject = new Document();
        projectData.stream().forEach(project -> {

            if(project.getFunction() != null){
                fieldObject.append(project.getAlias(), "$".concat(project.getAlias()));
            } else if(project.isCaseWhen()){
                fieldObject.append(project.getAlias(), ExpressionAnalyzer.buildCaseExpr(project.getCaseExpressionData(),tableNameManager));
            }else {

                // 字段携带表别名 例如 select t1.id,t2.name from
                if (StringUtils.isNotEmpty(project.getTable())) {
                    String table = project.getTable();
                    if (table.equals(majorTableAlias)) {
                        // 主表投影
                        fieldObject.append(project.getAlias(), "$".concat(project.getField()));

                    } else {

                        // 被关联表 需要携带 as （被关联表数据集）
                        LookUpData lookUpData = lookUpDataMap.get(project.getTable());
                        String target = lookUpData == null ? project.getField() : lookUpData.getAs().concat(".").concat(project.getField());
                        fieldObject.append(project.getField(), "$".concat(target));
                    }

                } else {
                    // 没有 字段携带的 就是单表
                    fieldObject.append(project.getAlias(), "$".concat(project.getField()));
                }

            }


        });
        if (fieldObject.size()!=0) {
            documents.add(new Document("$project", fieldObject));
        }
        return documents;
    }

}
